Appearance
Finally 1
本节目标:理解“Finally 1”的核心思路,并能把它用于实际开发或面试表达。
finally可以透传值,即:finally的参数函数如果返回一个promise:
- 如果这个
promise成功了,finally.then的成功回调会执行,但传递给成功回调的成功值为调用finally的promsie的成功值,而不是finally函数返回的promise的成功值;即finally函数的返回值会被丢弃; - 如果这个
promise失败了,finally.then的失败回调会执行,传递给失败回调的失败原因为这个promise的reject的失败原因;
实现: finally在promise状态不管是成功还是失败时,都要执行,理论上,我们可以在成功回调和失败回调中执行同样的代码来实现;但是由于要实现透传,所以不能简单地使用then(finallyArgFn,finallyArgFn)来实现;
Promise.prototype.finally= function
(cb){return
this.then((y)=\> {return
Promise.resolve(cb()).then(()=\>
y) `},`
(r)=\> {return
Promise.resolve(cb()).then(()=\> { throw r }); // 因为finally的promise执行出错, 会导致不会执行Promise.resolve的正常逻辑 ,所以以finally错误为结果
})
}
Promise.resolve('ok').finally(()=\> { // finally 并不会影响最终的结果 return new
Promise((resolve,reject)=\> {
setTimeout(()=\> {
resolve('innerok') `},`
1000);})
}).then((data)=\> {
console.log('成功
',data)
},(err)=\> {
console.log('失败
',err)
})finally在内部是调用了this.then函数,.then函数会返回一个promise,我们将这个promise作为finally的返回值返回出来,所以,finally后面是可以链式调用的;- 当
.finally时,表示对当前的promise使用then方法添加一个成功回调和失败回调; - 并且成功的回调函数和失败的回调函数内部都调用了
Promise.resolve方法; - 这个方法是是创建了一个
promise对象,并且具有等待效果的;所以,我们可以利用then给它添加成功回调和失败回调的; - 但我们这里只定义了成功回调,成功回调只是透传
finally前的成功值;如果finally的回调函数返回的promise对象状态是reject,相当于Promise.resolve这个promise状态失败,会调用then方法的失败回调,由于我们没有定义失败回调,是不会有任何反应的; - 这意味着,成功和失败的回调会等待
finally的参数函数的执行结果,如果finally参数返回一个promise,是会等待这个promise的;
